package com.google.code.opengw.server.initializer;

import java.io.File;
import java.io.IOException;

import javax.xml.parsers.ParserConfigurationException;

import org.w3c.dom.Document;
import org.w3c.dom.Element;
import org.w3c.dom.Node;
import org.w3c.dom.NodeList;
import org.xml.sax.SAXException;

import com.google.code.opengw.server.Constants;
import com.google.code.opengw.server.Server;
import com.google.code.opengw.server.domain.Domain;
import com.google.code.opengw.server.support.FileUtils;
import com.google.code.opengw.server.support.XMLParser;
import com.google.code.opengw.support.OpenGWException;
import com.google.code.opengw.support.OpenGWLogger;

public class DomainInitializer {
	
	DomainInitializer(){}
	
	void initialize(Document doc) throws OpenGWException, SAXException, IOException, ParserConfigurationException {
		Server server = Server.getInstance();
		NodeList domainNodeList = XMLParser.searchElementsFromDoc(doc,
				Constants.CONFIG_FILE_DOMAIN, new OpenGWException(
						OpenGWException.CONFIG_FILE_DOMAIN_NOT_FOUND));

		for (int i = 0; i < domainNodeList.getLength(); i++) {
			Node domainNode = domainNodeList.item(i);
			String domainName = ((Element) domainNode)
					.getAttribute(Constants.CONFIG_FILE_DOMAIN_NAME);
			if (domainName == null || domainName.equals(""))
				throw new OpenGWException(OpenGWException.format(
						OpenGWException.ATTRIBUTE_NOT_FOUND,
						Constants.CONFIG_FILE_DOMAIN,
						Constants.CONFIG_FILE_DOMAIN_NAME,
						Server.CONFIG_FILE_NAME));
			
			File domainPath = FileUtils.getDirectory(server.getDomainPath() + domainName);
				
			
			OpenGWLogger.addInfo(this.getClass(), domainName + " named domain initializing");
			String httpPort = ((Element) domainNode)
					.getAttribute(Constants.CONFIG_FILE_LISTENER_PORT);
			if (httpPort == null || httpPort.equals(""))
				throw new OpenGWException(OpenGWException.format(
						OpenGWException.ATTRIBUTE_NOT_FOUND,
						Constants.CONFIG_FILE_DOMAIN,
						Constants.CONFIG_FILE_LISTENER_PORT,
						Server.CONFIG_FILE_NAME));
			String initialWorkerCount = ((Element) domainNode)
					.getAttribute(Constants.CONFIG_FILE_DEFAULT_INITIAL_WORKER_COUNT);
			if (initialWorkerCount == null || initialWorkerCount.equals(""))
				initialWorkerCount = "" + server.getInitialWorkerCount();
			String workerIncreasementCount = ((Element) domainNode)
					.getAttribute(Constants.CONFIG_FILE_DEFAULT_WORKER_INCREASEMENT_COUNT);
			if (workerIncreasementCount == null
					|| workerIncreasementCount.equals(""))
				workerIncreasementCount = "" + server.getWorkerIncreasementCount();
			String maxWorkerCount = ((Element) domainNode)
					.getAttribute(Constants.CONFIG_FILE_DEFAULT_MAX_WORKER_COUNT);
			if (maxWorkerCount == null || maxWorkerCount.equals(""))
				maxWorkerCount = "" + server.getMaxWorkerCount();
			String connectionQueueSize = ((Element) domainNode)
					.getAttribute(Constants.CONFIG_FILE_DEFAULT_CONNECTION_QUEUE_SIZE);
			if (connectionQueueSize == null || connectionQueueSize.equals(""))
				connectionQueueSize = "" + server.getConnectionQueueSize();
			
			Domain domain = new Domain(domainName, Integer.parseInt(httpPort), Integer
					.parseInt(initialWorkerCount), Integer
					.parseInt(workerIncreasementCount), Integer
					.parseInt(maxWorkerCount), Integer
					.parseInt(connectionQueueSize));
			
			
			OpenGWLogger.addInfo(this.getClass(), "Publish List initialization starts");
			PublishInitializer publishInitializer = new PublishInitializer(domain);
			publishInitializer.initialize(domainPath);
			OpenGWLogger.addInfo(this.getClass(), "Publish List initialization successfullly finished");

			server.putDomain(domain);
		}
	}
}
